﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using viNews.Classes;
using visinia.SmartEngine.Cache;
using viNews.Providers;
using System.Data;

namespace viNews.Controllers
{
    public class CommentController
    {
        #region CACHE KEYS
        private const string KEY_COMMENTS_BY_NEWSID = "vinewscommentsByPostId_{0}";
        private const string KEY_COMMENTS_BY_COUNT = "vinewscommentsByCount_{0}";
        private const string KEY_UNAPPROVED_COMMENTS = "vinewscommentsUnApproved";
        private const string KEY_APPROVED_COMMENTS = "vinewscommentsApproved";
        private const string KEY_COMMENTS_COUNT = "vinewscommentsCount";
        #endregion

        /// <summary>
        /// Gets all the un approved comments
        /// </summary>        
        /// <returns>The unapproved comments</returns>
        public static List<Comment> GetUnapprovedComments()
        {
            string key = string.Format(KEY_UNAPPROVED_COMMENTS);
            List<Comment> list = (List<Comment>)DataCache.GetCache(key);
            if (list == null)
            {
                list = FillComments(viNewsDataProvider.Provider.GetUnapprovedComments());
                DataCache.SetCache(key, list, new System.TimeSpan(0, 20, 0));
            }
            return list;
        }

        /// <summary>
        /// Gets all the approved comments
        /// </summary>        
        /// <returns>The approved comments</returns>
        public static List<Comment> GetApprovedComments()
        {
            string key = string.Format(KEY_APPROVED_COMMENTS);
            List<Comment> list = (List<Comment>)DataCache.GetCache(key);
            if (list == null)
            {
                list = FillComments(viNewsDataProvider.Provider.GetApprovedComments());
                DataCache.SetCache(key, list, new System.TimeSpan(0, 20, 0));
            }
            return list;
        }

        /// <summary>
        /// Gets the approved comment
        /// </summary>        
        /// <returns>The approved comment</returns>
        public static Comment GetApprovedComment(int CommentId)
        {
            return GetApprovedComments().Find(p => p.CommentId == CommentId);
        }

        /// <summary>
        /// Gets the comments count of the specified news
        /// </summary>
        /// <param name="NewsId">The news id whose comment count to get</param>
        /// <returns>The count of the comments</returns>
        public static int GetCommentsCount(int NewsId)
        {
            DataCount data = GetCommentsCount().Find(p => p.DataId == NewsId);
            if (data != null)
                return data.Count;
            return 0;
        }

        private static List<DataCount> GetCommentsCount()
        {
            string key = string.Format(KEY_COMMENTS_COUNT);
            List<DataCount> list = (List<DataCount>)DataCache.GetCache(key);
            if (list == null)
            {
                list = FillCommentsCount(viNewsDataProvider.Provider.GetCommentsCount());
                DataCache.SetCache(key, list);
            }
            return list;
        }

        /// <summary>
        /// Gets all the comment of a specified news
        /// </summary>
        /// <param name="NewsId">The news whose comments to return</param>        
        /// <returns>The comments</returns>
        public static List<Comment> GetComments(int NewsId)
        {
            string key = string.Format(KEY_COMMENTS_BY_NEWSID, NewsId);
            List<Comment> list = (List<Comment>)DataCache.GetCache(key);
            if (list == null)
            {
                list = FillComments(viNewsDataProvider.Provider.GetComments(NewsId));
                DataCache.SetCache(key, list);
            }
            return list;
        }

        /// <summary>
        /// Gets the recent posted comments
        /// </summary>
        /// <param name="Count">Count of comments to return</param>
        /// <returns>The list of comments</returns>
        public static List<Comment> GetRecentComments(int Count)
        {
            string key = string.Format(KEY_COMMENTS_BY_COUNT, Count);
            List<Comment> list = (List<Comment>)DataCache.GetCache(key);
            if (list == null)
            {
                list = FillComments(viNewsDataProvider.Provider.GetRecentComments(Count));
                DataCache.SetCache(key, list);
            }
            return list;
        }

        #region DATA
        public static int AddComment(Comment comment)
        {
            IDataReader dr = viNewsDataProvider.Provider.AddComment(comment.NewsId, comment.Author, comment.Email, comment.Website, comment.Date, comment.Content, comment.IsApproved);
            int index = 0;
            while (dr.Read())
            {
                if (dr[0] != Convert.DBNull)
                    index = (int)dr[0];
            }
            dr.Close();
            DataCache.DeleteCacheMultiple("vinewscomment");
            return index;            
        }

        public static void DeleteComment(int CommentId)
        {
            viNewsDataProvider.Provider.DeleteComment(CommentId);
            DataCache.DeleteCacheMultiple("vinewscomment");
        }

        public static void ApproveComment(int CommentId)
        {
            viNewsDataProvider.Provider.ApproveComment(CommentId);
            DataCache.DeleteCacheMultiple("vinewscomment");
        }

        public static void DeleteComments(int PostId)
        {
            viNewsDataProvider.Provider.DeleteComments(PostId);
            DataCache.DeleteCacheMultiple("vinewscomment");
        }
        #endregion

        #region HELPERS
        private static List<DataCount> FillCommentsCount(IDataReader dr)
        {
            List<DataCount> list = new List<DataCount>();
            while (dr.Read())
            {
                list.Add(ActualReadCommentsCount(dr));
            }
            dr.Close();
            return list;
        }
        private static DataCount ActualReadCommentsCount(IDataReader dr)
        {
            DataCount data = new DataCount();
            if (dr["DataId"] != Convert.DBNull)
                data.DataId = (int)dr["DataId"];
            if (dr["Count"] != Convert.DBNull)
                data.Count = (int)dr["Count"];
            return data;
        }

        private static List<Comment> FillComments(IDataReader dr)
        {
            List<Comment> list = new List<Comment>();
            while (dr.Read())
            {
                list.Add(ActualRead(dr));
            }
            dr.Close();
            return list;
        }

        private static Comment ActualRead(IDataReader dr)
        {
            Comment comment = new Comment();
            if (dr["CommentId"] != Convert.DBNull)
                comment.CommentId = (int)dr["CommentId"];
            if (dr["NewsId"] != Convert.DBNull)
                comment.NewsId = (int)dr["NewsId"];
            if (dr["Author"] != Convert.DBNull)
                comment.Author = (string)dr["Author"];
            if (dr["Email"] != Convert.DBNull)
                comment.Email = (string)dr["Email"];
            if (dr["Website"] != Convert.DBNull)
                comment.Website = (string)dr["Website"];
            if (dr["Date"] != Convert.DBNull)
                comment.Date = (DateTime)dr["Date"];
            if (dr["CommentContent"] != Convert.DBNull)
                comment.Content = (string)dr["CommentContent"];
            if (dr["IsApproved"] != Convert.DBNull)
                comment.IsApproved = (bool)dr["IsApproved"];
            return comment;
        }
        #endregion
    }
}
